#!/usr/bin/env python3
"""
Modular Trading Bot - Supports multiple exchanges
"""

import argparse
import asyncio
from decimal import Decimal
from trading_bot import TradingBot, TradingConfig
from exchanges import ExchangeFactory


def parse_arguments():
    """Parse command line arguments."""
    parser = argparse.ArgumentParser(description='Modular Trading Bot - Supports multiple exchanges')

    # Exchange selection
    parser.add_argument('--exchange', type=str, default='edgex',
                        choices=ExchangeFactory.get_supported_exchanges(),
                        help='Exchange to use (default: edgex). '
                             f'Available: {", ".join(ExchangeFactory.get_supported_exchanges())}')

    # Trading parameters
    parser.add_argument('--ticker', type=str, default='ETH',
                        help='Ticker (default: ETH)')
    parser.add_argument('--quantity', type=Decimal, default=Decimal(0.1),
                        help='Order quantity (default: 0.1)')
    parser.add_argument('--take-profit', type=Decimal, default=Decimal(0.02),
                        help='Take profit in USDT (default: 0.02)')
    parser.add_argument('--leverage', type=int, default=3,
                        help='Leverage multiplier for exchanges that require notional thresholds (default: 3)')
    parser.add_argument('--direction', type=str, default='buy',
                        help='Direction of the bot (default: buy)')
    parser.add_argument('--max-orders', type=int, default=40,
                        help='Maximum number of active orders (default: 40)')
    parser.add_argument('--wait-time', type=int, default=450,
                        help='Wait time between orders in seconds (default: 450)')
    # Multi-account support
    parser.add_argument('--keys', type=str, default='',
                        help='Comma-separated list of private keys for multi-account concurrent bots')
    parser.add_argument('--keys-file', type=str, default='./keys.txt',
                        help='Path to a file containing one private key per line')
    # EdgeX cancel-all and close-all-positions for all accounts in keys
    parser.add_argument('--edgex-cancel-all', action='store_true',
                        help='For exchange edgex: cancel all active orders for all accounts from keys/keys-file and exit')
    parser.add_argument('--edgex-close-all-positions', action='store_true',
                        help='For exchange edgex: close all open positions (flatten) for all accounts from keys/keys-file and exit')

    return parser.parse_args()


async def main():
    """Main entry point."""
    args = parse_arguments()

    # Collect keys
    keys = []
    if args.keys:
        keys += [k.strip() for k in args.keys.split(',') if k.strip()]
    if args.keys_file:
        try:
            with open(args.keys_file, 'r') as f:
                for line in f:
                    k = line.strip()
                    if k:
                        keys.append(k)
        except Exception as e:
            print(f"Failed to read keys-file: {e}")

    # If no keys provided, run single bot (env-based)
    if not keys:
        config = TradingConfig(
            ticker=args.ticker,
            contract_id='',  # will be set in the bot's run method
            tick_size=Decimal(0),
            quantity=args.quantity,
            take_profit=args.take_profit,
            leverage=args.leverage,
            direction=args.direction,
            max_orders=args.max_orders,
            wait_time=args.wait_time,
            exchange=args.exchange,
            private_key=None,
            edgex_account_id=None,
            edgex_stark_private_key=None
        )
        bot = TradingBot(config)
        try:
            await bot.run()
        except Exception as e:
            print(f"Bot execution failed: {e}")
            return
    else:
        # Run multiple bots concurrently
        async def run_one(pk: str):
            cfg = TradingConfig(
                ticker=args.ticker,
                contract_id='',
                tick_size=Decimal(0),
                quantity=args.quantity,
                take_profit=args.take_profit,
                leverage=args.leverage,
                direction=args.direction,
                max_orders=args.max_orders,
                wait_time=args.wait_time,
                exchange=args.exchange,
                private_key=pk if args.exchange == 'ostium' else None,
                edgex_account_id=pk.split(':')[0] if args.exchange == 'edgex' and ':' in pk else None,
                edgex_stark_private_key=pk.split(':')[1] if args.exchange == 'edgex' and ':' in pk else None
            )
            if args.exchange == 'edgex' and (args.edgex_cancel_all or args.edgex_close_all_positions):
                from exchanges import ExchangeFactory
                client = ExchangeFactory.create_exchange('edgex', cfg)
                try:
                    await client.connect()
                    if args.edgex_cancel_all and hasattr(client, 'cancel_all_orders'):
                        await client.cancel_all_orders()
                    if args.edgex_close_all_positions and hasattr(client, 'close_all_positions'):
                        await client.close_all_positions()
                finally:
                    try:
                        await client.disconnect()
                    except Exception:
                        pass
            else:
                bot = TradingBot(cfg)
                await bot.run()

        tasks = [asyncio.create_task(run_one(pk)) for pk in keys]
        try:
            await asyncio.gather(*tasks)
        except Exception as e:
            print(f"One of the bots failed: {e}")


if __name__ == "__main__":
    asyncio.run(main())
